import uvicorn
from fastapi import FastAPI
from fastapi.middleware.cors import CORSMiddleware
from fastapi.staticfiles import StaticFiles
from contextlib import asynccontextmanager
import router_static_html
import router_module    
from config import *
from sense_voice_small_asr import load_model, transcribe_audio, asr_router
from audio_websocket import router as websocket_router     

@asynccontextmanager
async def lifespan(app: FastAPI):
    # 根据配置决定是否挂载静态文件目录
    if enable_static_files:
        print(f"挂载静态文件目录: {static_files_directory} -> {static_files_url}")
        app.mount(static_files_url, StaticFiles(directory=static_files_directory), name="static")
    else:
        print("静态文件目录挂载已禁用")
    
    # 尝试加载模型
    from sense_voice_small_asr import global_model, check_model_cache, cache_dir
    if global_model is None:
        print("正在预加载模型...")
        try:
            # 检查模型是否已缓存
            model_cached = check_model_cache(asr_model_dir, cache_dir)
            punc_cached = check_model_cache(asr_punc_model_dir, cache_dir)
            vad_cached = check_model_cache(asr_vad_model_dir, cache_dir)
            
            if model_cached:
                print(f"模型已缓存: {asr_model_dir}")
            if punc_cached:
                print(f"标点模型已缓存: {asr_punc_model_dir}")
            if vad_cached:
                print(f"VAD模型已缓存: {asr_vad_model_dir}")
            
            # 先尝试使用配置中的本地模型路径
            from sense_voice_small_asr import load_model
            global_model = load_model()
            print("模型预加载完成")
        except Exception as e:
            print(f"使用本地模型预加载失败: {str(e)}")
            try:
                # 检查备用模型是否已缓存
                backup_model_cached = check_model_cache(asr_model_dir_backup, cache_dir)
                backup_punc_cached = check_model_cache(asr_punc_model_dir_backup, cache_dir)
                backup_vad_cached = check_model_cache(asr_vad_model_dir_backup, cache_dir)
                
                if backup_model_cached:
                    print(f"备用模型已缓存: {asr_model_dir_backup}")
                if backup_punc_cached:
                    print(f"备用标点模型已缓存: {asr_punc_model_dir_backup}")
                if backup_vad_cached:
                    print(f"备用VAD模型已缓存: {asr_vad_model_dir_backup}")
                
                # 尝试使用备用模型
                print("尝试使用备用模型...")
                global_model = load_model(
                    model_dir=asr_model_dir_backup, 
                    punc_model_dir=asr_punc_model_dir_backup, 
                    vad_model_dir=asr_vad_model_dir_backup
                )
                print("使用备用模型预加载完成")
            except Exception as backup_error:
                print(f"使用备用模型预加载失败: {str(backup_error)}")
                print("应用将在首次请求时尝试加载模型")
        
    yield
    # 关闭时的清理代码可以放在这里

# 创建FastAPI应用
app = FastAPI(
    title=app_name,
    description=app_description,
    version=app_version,
    lifespan=lifespan
)

# 添加CORS中间件
app.add_middleware(
    CORSMiddleware,
    allow_origins=["*"],  # 允许所有来源，生产环境中应该设置为特定的域名
    allow_credentials=True,
    allow_methods=["*"],  # 允许所有方法
    allow_headers=["*"],  # 允许所有头
)


app.include_router(router_module.router_module_real, prefix=router_dict["router_module"])
app.include_router(router_static_html.router_html_real, prefix=router_dict["router_html"])
app.include_router(asr_router, prefix="/funasr", tags=["语音识别"])
# 包含WebSocket路由器
app.include_router(websocket_router, prefix="/ws")

# 添加根路径重定向到主页
@app.get("/")
async def root():
    from fastapi.responses import RedirectResponse
    # 如果静态文件目录已挂载，重定向到静态页面，否则重定向到API文档
    if enable_static_files:
        return RedirectResponse(url=f"{static_files_url}/index.html")
    else:
        return RedirectResponse(url="/docs")

# 添加API文档路径
@app.get("/api-docs")
async def api_docs():
    from fastapi.responses import RedirectResponse
    return RedirectResponse(url="/docs")

if __name__ == "__main__":
    # 启动FastAPI服务
    uvicorn.run(app, host=app_host, port=app_port) 
